package com.dcoinpay.sys.controller;

import io.swagger.annotations.Api;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.quartz.TriggerUtils;
import org.quartz.impl.triggers.CronTriggerImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.servlet.ModelAndView;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.dcoinpay.common.aop.annotation.LogAnnotation;
import com.dcoinpay.common.exception.code.BaseResponseCode;
import com.dcoinpay.common.job.utils.ScheduleJob;
import com.dcoinpay.common.utils.DataResult;
import com.dcoinpay.sys.entity.SysJobEntity;
import com.dcoinpay.sys.service.SysJobService;
import com.baomidou.mybatisplus.core.metadata.IPage;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

/**
 * 定时任务
 *
 * @author wenbin
 * @version V1.0
 * @date 2020年3月18日
 */
@Api(tags = "定时任务")
@RestController
@RequestMapping("/sys/job")
public class JobController {
	@Autowired
	private SysJobService sysJobService;
	
    /**
    * 跳转到页面
    */
    @GetMapping("/listview")
    public ModelAndView listview() {
        return new ModelAndView("sys/job/list");
    }

	@ApiOperation(value = "新增")
	@LogAnnotation(title = "新增")
	@PostMapping("/add")
	@RequiresPermissions("sys:job:add")
	public DataResult<SysJobEntity> add(@RequestBody SysJobEntity sysJob) {
		if (!isValidExpression(sysJob.getCronExpression())) {
			return DataResult.fail("cron表达式有误");
		}
		DataResult<SysJobEntity> dataResult = ScheduleJob.judgeBean(sysJob.getBeanName());
		if (BaseResponseCode.SUCCESS.getCode() != dataResult.getCode()) {
			return dataResult;
		}

		sysJobService.saveJob(sysJob);
		return DataResult.success();
	}

	@ApiOperation(value = "删除")
	@DeleteMapping("/delete")
	@RequiresPermissions("sys:job:delete")
	@LogAnnotation(title = "删除")
	public DataResult<Object> delete(@RequestBody @ApiParam(value = "id集合") List<String> ids) {
		sysJobService.delete(ids);
		return DataResult.success();
	}

	@ApiOperation(value = "更新")
	@PutMapping("/update")
	@RequiresPermissions("sys:job:update")
	@LogAnnotation(title = "更新")
	public DataResult<SysJobEntity> update(@RequestBody SysJobEntity sysJob) {
		if (!isValidExpression(sysJob.getCronExpression())) {
			return DataResult.fail("cron表达式有误");
		}
		DataResult<SysJobEntity> dataResult = ScheduleJob.judgeBean(sysJob.getBeanName());
		if (BaseResponseCode.SUCCESS.getCode() != dataResult.getCode()) {
			return dataResult;
		}

		sysJobService.updateJobById(sysJob);
		return DataResult.success();
	}

	@ApiOperation(value = "查询分页数据")
	@PostMapping("/list")
	@RequiresPermissions("sys:job:list")
	public DataResult<Object> findListByPage(@RequestBody SysJobEntity sysJob) {
		Page<SysJobEntity> page = new Page<SysJobEntity>(sysJob.getPage(), sysJob.getLimit());
		QueryWrapper<SysJobEntity> queryWrapper = new QueryWrapper<SysJobEntity>();
		//查询条件示例
		if (!StringUtils.isEmpty(sysJob.getBeanName())) {
			queryWrapper.like("bean_name", sysJob.getBeanName());
		}
		IPage<SysJobEntity> iPage = sysJobService.page(page, queryWrapper);
		return DataResult.success(iPage);
	}

	/**
	 * 立即执行任务
	 */
	@ApiOperation(value = "立即执行任务")
	@LogAnnotation(title = "立即执行任务")
	@PostMapping("/run")
	@RequiresPermissions("sys:job:run")
	public DataResult<Object> run(@RequestBody List<String> ids) {
		sysJobService.run(ids);

		return DataResult.success();
	}

	/**
	 * 暂停定时任务
	 */
	@ApiOperation(value = "暂停定时任务")
	@LogAnnotation(title = "暂停定时任务")
	@PostMapping("/pause")
	@RequiresPermissions("sys:job:pause")
	public DataResult<Object> pause(@RequestBody List<String> ids) {
		sysJobService.pause(ids);

		return DataResult.success();
	}

	/**
	 * 恢复定时任务
	 */
	@ApiOperation(value = "恢复定时任务")
	@LogAnnotation(title = "恢复定时任务")
	@PostMapping("/resume")
	@RequiresPermissions("sys:job:resume")
	public DataResult<Object> resume(@RequestBody List<String> ids) {
		sysJobService.resume(ids);

		return DataResult.success();
	}

	public static boolean isValidExpression(String cronExpression) {
		CronTriggerImpl trigger = new CronTriggerImpl();
		try {
			trigger.setCronExpression(cronExpression);
			Date date = trigger.computeFirstFireTime(null);
			return date != null && date.after(new Date());
		} catch (Exception e) {
			return false;
		}
	}

	@ApiOperation(value = "获取运行时间")
	@LogAnnotation(title = "获取运行时间")
	@GetMapping("/getRecentTriggerTime")
	@RequiresPermissions("sys:job:add")
	public DataResult<Object> getRecentTriggerTime(String cron) {
		List<String> list = new ArrayList<String>();
		try {
			CronTriggerImpl cronTriggerImpl = new CronTriggerImpl();
			cronTriggerImpl.setCronExpression(cron);
			// 这个是重点，一行代码搞定
			List<Date> dates = TriggerUtils.computeFireTimes(cronTriggerImpl, null, 5);
			SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
			for (Date date : dates) {
				list.add(dateFormat.format(date));
			}

		} catch (ParseException e) {
			e.printStackTrace();
		}
		return DataResult.success(list);
	}

}
